home *** CD-ROM | disk | FTP | other *** search
/ Mac-Source 1994 July / Mac-Source_July_1994.iso / C and C++ / Science⁄Math / VideoToolbox / VideoToolboxSources / GetScreenDevice.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-08-14  |  5.9 KB  |  179 lines  |  [TEXT/KAHL]

  1. /* GetScreenDevice.c
  2. PROBLEM:
  3. How can I tell whether I've got a CGrafPtr or a GWorldPtr? (In one case I'll call 
  4. GetGWorldDevice, in the other case I'll get max device.)
  5. I noticed that the portVersions are 0xc001 and 0xc000. Should I use that to tell?
  6.  
  7. ANSWER FROM APPLE DEVSUPPORT (8/93):
  8. You can use GetGWorldDevice() on GWorldPtr, GrafPort or CGrafPort. Use
  9. TestDeviceAttibute() to test if the returned GDHandle is a "real" screen or not.
  10.  
  11. Also, you should refer to the tech note “RowBytes Revealed II” (available on the
  12. June Developer CD) which states:
  13.  
  14. You'll notice in Figure 1 that the portVersion field of a cGrafPort coincides
  15. with the location of the rowBytes field of a grafPort. Remember, a cGrafPort has
  16. the same size as a grafPort. During debugging, you can use the same information
  17. which CopyBits uses to identify cGrafPorts.
  18.  
  19. If you use a grafPort template to display memory for an unknown grafPort, you
  20. can tell if it is a cGrafPort because the rowBytes will be equal to 0xC000. The
  21. 0xC corresponds to the two high bits being set in the portVersion field of a
  22. cGrafPort. Since these bits can not be set in a grafPort, you know you have a
  23. cGrafPort. In addition, if the bottom bit of the portVersion field is set, then
  24. it is a gWorld. Thus, if your rowBytes field has a value of 0xC001, then you
  25. know you have a gWorld.
  26.  
  27. CONCLUSION:
  28. GetWindowDevice() assumes that it's a GWorld iff the bits 0xC001 of the
  29. are set. From Apple's comment above this is clearly true at present and probably
  30. safe for the future.
  31.  
  32. Copyright © 1989-1993 Denis G. Pelli
  33. HISTORY:
  34. 3/20/90        dgp    make compatible with MPW C.
  35. 3/22/90    dgp    changed GetDeviceSlot to use the AuxDCEHandle instead of deducing it
  36.             from the baseAddr of the PixMap. This is a cleaner way to do it.
  37. 4/9/90    dgp    eliminated #define for Mainscrn mispelling in Color.h
  38. 10/17/90 dgp Added AddressToScreenDevice() for compatibility with built-in video on
  39.             the Mac IIci, IIsi, and LC.
  40. 10/18/90 dgp Added LocalToGlobalRect() and GetWindowDevice().
  41. 8/24/91        dgp    Made compatible with THINK C 5.0.
  42. 2/1/92    dgp    Fixed bugs in GetWindowDevice() which resulted in returning garbage GDHandle.
  43. 3/3/92    dgp    In GetScreenDevice(), skip inactive screens.
  44. 8/20/92    dgp    expanded comments of GetDeviceSlot(), noting that it works even with
  45.             built-in video, e.g. on Mac IIci.
  46. 8/26/92    dgp    GetDeviceSlot() now returns -1 if none, since zero is a legal slot.
  47.             GetScreenDevice() first checks for 8-bit QuickDraw().
  48. 9/10/92    dgp    Actually implemented the 8/26 change instead of just changing the 
  49.             documentation. Oops.
  50. 4/17/93    dgp Deleted obsolete AddressToSlot and AddressToScreenDevice.
  51. 5/21/93    dgp    Fixed GetWindowDevice() to support GWorld's.
  52. 8/14/93    dgp    Based on answer from DEVSUPPORT, I cleaned up GetWindowDevice().
  53. */
  54. #include "VideoToolbox.h"
  55.  
  56. GDHandle GetScreenDevice(int n)
  57. // Returns a handle to the n-th screen, where the MainDevice is the zero-th screen.
  58. // Returns NULL if request can't be satisfied.
  59. {
  60.     GDHandle device;
  61.     int i,error;
  62.     long value;
  63.  
  64.     if(n<0)return NULL;
  65.     error=Gestalt(gestaltQuickdrawVersion,&value);
  66.     if(error || value<gestalt8BitQD)return NULL;    // need 8-bit quickdraw
  67.     if(n==0) return GetMainDevice();
  68.     device=GetDeviceList();
  69.     i=0;
  70.     while(device!=NULL){
  71.         if (TestDeviceAttribute(device,screenDevice)
  72.             && !TestDeviceAttribute(device,mainScreen)
  73.             && TestDeviceAttribute(device,screenActive)){
  74.                 i++;
  75.                 if(i==n)break;
  76.             }
  77.         device = GetNextDevice(device);
  78.     }
  79.     return device;
  80. }
  81.  
  82. int GetScreenIndex(GDHandle device)
  83. // Inverse of GetScreenDevice(). Returns -1 if request can't be satisfied.
  84. {
  85.     int i,error;
  86.     long value;
  87.  
  88.     error=Gestalt(gestaltQuickdrawVersion,&value);
  89.     if(error || value<gestalt8BitQD)return 0;
  90.     if(device==NULL)return -1;
  91.     for(i=0;i<16;i++)if(device==GetScreenDevice(i))return i;
  92.     return -1;
  93. }
  94.  
  95. short int GetDeviceSlot(GDHandle device)
  96. // Gets the "slot" for any screen device, even if it's built-in video, e.g. on Mac
  97. // IIci or Quadra. See 1992 Inside Mac "Processes" page 4-11. Returns -1 if none.
  98. // Zero is a legal slot for built-in video devices.
  99. {
  100.     AuxDCEHandle myAuxDCEHandle;
  101.  
  102.     if(device == NULL) return -1;
  103.     myAuxDCEHandle=(AuxDCEHandle) GetDCtlEntry((**device).gdRefNum);
  104.     return ((**myAuxDCEHandle).dCtlSlot);
  105. }
  106.  
  107. GDHandle SlotToScreenDevice(int n)
  108. // Returns a handle to the screen device in slot n.
  109. // Returns NULL if request can't be satisfied.
  110. {
  111.     GDHandle device;
  112.  
  113.     device=GetDeviceList();
  114.     while(device!=NULL) {
  115.         if (TestDeviceAttribute(device,screenDevice) &&
  116.             GetDeviceSlot(device)==n)
  117.                 break;
  118.         device=GetNextDevice(device);
  119.     }
  120.     return device;
  121. }
  122.  
  123. GDHandle GetWindowDevice(WindowPtr window)
  124. // For on-screen window, returns GDHandle of screen with largest intersection with the 
  125. // window's content.
  126. // For off-screen window (i.e. GWorld), it returns the GDHandle of the associated device.
  127. {
  128.     Rect r,overlap;
  129.     GDHandle device,dominantDevice=NULL;
  130.     long area,greatestArea;
  131.     WindowPtr oldWindow;
  132.     int error;
  133.     long qD;
  134.  
  135.     if(window==NULL)return NULL;
  136.     error=Gestalt(gestaltQuickdrawVersion,&qD);
  137.     if(error || qD<gestalt8BitQD)return NULL;    // need 8-bit quickdraw
  138.     if(qD>=gestalt32BitQD && (((CWindowPtr)window)->portVersion&0xc001)==0xc001){
  139.         // It's a GWorld iff the portVersion has both high bits set (cGrafPort) and
  140.         // the low bit set (GWorld). See Tech Note “RowBytes Revealed II”.
  141.         return GetGWorldDevice((GWorldPtr)window);
  142.     }
  143.     r=window->portRect;
  144.     GetPort(&oldWindow);
  145.     SetPort(window);
  146.     LocalToGlobalRect(&r);
  147.     SetPort(oldWindow);
  148.     device=GetDeviceList();
  149.     greatestArea=0;
  150.     while(device!=NULL){
  151.         if(TestDeviceAttribute(device,screenDevice)
  152.             && TestDeviceAttribute(device,screenActive)){
  153.                 SectRect(&r,&(*device)->gdRect,&overlap);
  154.                 area=(long)(overlap.right-overlap.left)*(overlap.bottom-overlap.top);
  155.                 if(area>greatestArea){
  156.                     greatestArea=area;
  157.                     dominantDevice=device;
  158.                 }
  159.             }
  160.         device=GetNextDevice(device);
  161.     }
  162.     return dominantDevice;
  163. }
  164.  
  165. void LocalToGlobalRect(Rect *r)
  166. {
  167.     Point pt={0,0};
  168.     
  169.     LocalToGlobal(&pt);
  170.     OffsetRect(r,pt.h,pt.v);
  171. }
  172.  
  173. void GlobalToLocalRect(Rect *r)
  174. {
  175.     Point pt={0,0};
  176.     
  177.     GlobalToLocal(&pt);
  178.     OffsetRect(r,pt.h,pt.v);
  179. }